#ifndef __PINFUN_H
#define __PINFUN_H

#include "bsp.h"
#include "pintype.h"

#ifdef __cplusplus
extern "C"
{
#endif

/*******************************************************************************
 * @brief   IO位带区映射
 *******************************************************************************/
#define BITBAND(addr, bitnum) ((addr & 0xF0000000) + 0x2000000 + ((addr & 0xFFFFF) << 5) + (bitnum << 2))
#define MEM_ADDR(addr) *((volatile unsigned long *)(addr))
#define BIT_ADDR(addr, bitnum) MEM_ADDR(BITBAND(addr, bitnum))

// IO口地址映射
#define GPIOA_ODR_Addr (GPIOA_BASE + 0x14)
#define GPIOB_ODR_Addr (GPIOB_BASE + 0x14)
#define GPIOC_ODR_Addr (GPIOC_BASE + 0x14)
#define GPIOD_ODR_Addr (GPIOD_BASE + 0x14)
#define GPIOE_ODR_Addr (GPIOE_BASE + 0x14)
#define GPIOF_ODR_Addr (GPIOF_BASE + 0x14)
#define GPIOG_ODR_Addr (GPIOG_BASE + 0x14)
#define GPIOH_ODR_Addr (GPIOH_BASE + 0x14)

#define GPIOA_IDR_Addr (GPIOA_BASE + 0x10)
#define GPIOB_IDR_Addr (GPIOB_BASE + 0x10)
#define GPIOC_IDR_Addr (GPIOC_BASE + 0x10)
#define GPIOD_IDR_Addr (GPIOD_BASE + 0x10)
#define GPIOE_IDR_Addr (GPIOE_BASE + 0x10)
#define GPIOF_IDR_Addr (GPIOF_BASE + 0x10)
#define GPIOG_IDR_Addr (GPIOG_BASE + 0x10)
#define GPIOH_IDR_Addr (GPIOH_BASE + 0x10)

// IO口操作,只对单一的IO口
#define PAout(n) BIT_ADDR(GPIOA_ODR_Addr, n) // 输出
#define PAin(n) BIT_ADDR(GPIOA_IDR_Addr, n)	 // 输入

#define PBout(n) BIT_ADDR(GPIOB_ODR_Addr, n) // 输出
#define PBin(n) BIT_ADDR(GPIOB_IDR_Addr, n)	 // 输入

#define PCout(n) BIT_ADDR(GPIOC_ODR_Addr, n) // 输出
#define PCin(n) BIT_ADDR(GPIOC_IDR_Addr, n)	 // 输入

#define PDout(n) BIT_ADDR(GPIOD_ODR_Addr, n) // 输出
#define PDin(n) BIT_ADDR(GPIOD_IDR_Addr, n)	 // 输入

#define PEout(n) BIT_ADDR(GPIOE_ODR_Addr, n) // 输出
#define PEin(n) BIT_ADDR(GPIOE_IDR_Addr, n)	 // 输入

#define PFout(n) BIT_ADDR(GPIOF_ODR_Addr, n) // 输出
#define PFin(n) BIT_ADDR(GPIOF_IDR_Addr, n)	 // 输入

#define PGout(n) BIT_ADDR(GPIOG_ODR_Addr, n) // 输出
#define PGin(n) BIT_ADDR(GPIOG_IDR_Addr, n)	 // 输入

/*******************************************************************************
 * @brief   端口
 *******************************************************************************/
#define PA_PORT GPIOA
#define PB_PORT GPIOB
#define PC_PORT GPIOC
#define PD_PORT GPIOD
#define PE_PORT GPIOE
#define PF_PORT GPIOF
#define PG_PORT GPIOG
#define PH_PORT GPIOH

	/*******************************************************************************
	 * @brief   功能
	 *******************************************************************************/
	void bsp_gpio_mode_out_pp(gpio_type *port, uint8_t pin);
	void bsp_gpio_mode_out_od(gpio_type *port, uint8_t pin);
	void bsp_gpio_mode_in_up(gpio_type *port, uint8_t pin);
	void bsp_gpio_mode_in_dn(gpio_type *port, uint8_t pin);
	void bsp_gpio_mode_in_ft(gpio_type *port, uint8_t pin);
	void bsp_gpio_mode_set(gpio_type *port, uint8_t pin, char pm);

#define gpio_out_high(port, pin) port##out(pin) = 1
#define gpio_out_low(port, pin) port##out(pin) = 0
#define gpio_out_tog(port, pin) port##out(pin) = !port##out(pin)
#define gpio_out_set(port, pin, st) port##out(pin) = (st)
#define gpio_out_get(port, pin) port##out(pin)
#define gpio_in_get(port, pin) port##in(pin)

#define gpio_mode_set(port, pin, pm) bsp_gpio_mode_set(port##_PORT, pin, pm)
#define gpio_dir_in_ft(port, pin) bsp_gpio_mode_in_ft(port##_PORT, pin)
#define gpio_dir_in_dn(port, pin) bsp_gpio_mode_in_dn(port##_PORT, pin)
#define gpio_dir_in_up(port, pin) bsp_gpio_mode_in_up(port##_PORT, pin)
#define gpio_dir_out_pp(port, pin) bsp_gpio_mode_out_pp(port##_PORT, pin)
#define gpio_dir_out_od(port, pin) bsp_gpio_mode_out_od(port##_PORT, pin)

/*******************************************************************************
 * @brief   同相IO定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_simp_pin_make(name, port, pin) \
	extern const port_simp_pin_type name
#else
#define port_simp_pin_make(name, port, pin) \
                                            \
	void name##_pin_en(void);               \
	void name##_pin_dis(void);              \
	void name##_pin_out(uint8_t st);        \
	uint8_t name##_pin_out_st(void);        \
	uint8_t name##_pin_in_st(void);         \
                                            \
	void name##_pin_en(void)                \
	{                                       \
		gpio_out_high(port, pin);           \
	}                                       \
	void name##_pin_dis(void)               \
	{                                       \
		gpio_out_low(port, pin);            \
	}                                       \
	void name##_pin_out(uint8_t st)         \
	{                                       \
		gpio_out_set(port, pin, st);        \
	}                                       \
	uint8_t name##_pin_out_st(void)         \
	{                                       \
		return gpio_out_get(port, pin);     \
	}                                       \
	uint8_t name##_pin_in_st(void)          \
	{                                       \
		return gpio_in_get(port, pin);      \
	}                                       \
	const port_simp_pin_type name = {       \
		name##_pin_en,                      \
		name##_pin_dis,                     \
		name##_pin_out,                     \
		name##_pin_out_st,                  \
		name##_pin_in_st}
#endif

/*******************************************************************************
 * @brief   反相IO定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_nsimp_pin_make(name, port, pin) \
	extern const port_simp_pin_type name
#else
#define port_nsimp_pin_make(name, port, pin) \
                                             \
	void name##_pin_en(void);                \
	void name##_pin_dis(void);               \
	void name##_pin_out(uint8_t st);         \
	uint8_t name##_pin_out_st(void);         \
	uint8_t name##_pin_in_st(void);          \
                                             \
	void name##_pin_en(void)                 \
	{                                        \
		gpio_out_low(port, pin);             \
	}                                        \
	void name##_pin_dis(void)                \
	{                                        \
		gpio_out_high(port, pin);            \
	}                                        \
	void name##_pin_out(uint8_t st)          \
	{                                        \
		gpio_out_set(port, pin, !st);        \
	}                                        \
	uint8_t name##_pin_out_st(void)          \
	{                                        \
		return !gpio_out_get(port, pin);     \
	}                                        \
	uint8_t name##_pin_in_st(void)           \
	{                                        \
		return !gpio_in_get(port, pin);      \
	}                                        \
	const port_simp_pin_type name = {        \
		name##_pin_en,                       \
		name##_pin_dis,                      \
		name##_pin_out,                      \
		name##_pin_out_st,                   \
		name##_pin_in_st}
#endif

/*******************************************************************************
 * @brief   同相IO定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_fun_pin_make(name, port, pin) \
	extern const port_fun_pin_type name
#else
#define port_fun_pin_make(name, port, pin) \
                                           \
	void name##_pin_en(void);              \
	void name##_pin_dis(void);             \
	void name##_pin_out(uint8_t st);       \
	void name##_pin_tog(void);             \
	uint8_t name##_pin_out_st(void);       \
	uint8_t name##_pin_in_st(void);        \
	void name##_mode_set(char pm);         \
                                           \
	void name##_pin_en(void)               \
	{                                      \
		gpio_out_high(port, pin);          \
	}                                      \
	void name##_pin_dis(void)              \
	{                                      \
		gpio_out_low(port, pin);           \
	}                                      \
	void name##_pin_out(uint8_t st)        \
	{                                      \
		gpio_out_set(port, pin, st);       \
	}                                      \
	void name##_pin_tog(void)              \
	{                                      \
		gpio_out_tog(port, pin);           \
	}                                      \
	uint8_t name##_pin_out_st(void)        \
	{                                      \
		return gpio_out_get(port, pin);    \
	}                                      \
	uint8_t name##_pin_in_st(void)         \
	{                                      \
		return gpio_in_get(port, pin);     \
	}                                      \
	void name##_mode_set(char pm)          \
	{                                      \
		gpio_mode_set(port, pin, pm);      \
	}                                      \
	const port_fun_pin_type name = {       \
		name##_pin_en,                     \
		name##_pin_dis,                    \
		name##_pin_out,                    \
		name##_pin_tog,                    \
		name##_pin_out_st,                 \
		name##_pin_in_st,                  \
		name##_mode_set}
#endif

/*******************************************************************************
 * @brief   反相IO定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_nfun_pin_make(name, port, pin) \
	extern const port_fun_pin_type name
#else
#define port_nfun_pin_make(name, port, pin) \
                                            \
	void name##_pin_en(void);               \
	void name##_pin_dis(void);              \
	void name##_pin_out(uint8_t st);        \
	void name##_pin_tog(void);              \
	uint8_t name##_pin_out_st(void);        \
	uint8_t name##_pin_in_st(void);         \
	void name##_mode_set(char pm);          \
                                            \
	void name##_pin_en(void)                \
	{                                       \
		gpio_out_low(port, pin);            \
	}                                       \
	void name##_pin_dis(void)               \
	{                                       \
		gpio_out_high(port, pin);           \
	}                                       \
	void name##_pin_out(uint8_t st)         \
	{                                       \
		gpio_out_set(port, pin, !st);       \
	}                                       \
	void name##_pin_tog(void)               \
	{                                       \
		gpio_out_tog(port, pin);            \
	}                                       \
	uint8_t name##_pin_out_st(void)         \
	{                                       \
		return !gpio_out_get(port, pin);    \
	}                                       \
	uint8_t name##_pin_in_st(void)          \
	{                                       \
		return !gpio_in_get(port, pin);     \
	}                                       \
	void name##_mode_set(char pm)           \
	{                                       \
		gpio_mode_set(port, pin, pm);       \
	}                                       \
	const port_fun_pin_type name = {        \
		name##_pin_en,                      \
		name##_pin_dis,                     \
		name##_pin_out,                     \
		name##_pin_tog,                     \
		name##_pin_out_st,                  \
		name##_pin_in_st,                   \
		name##_mode_set}
#endif

/*******************************************************************************
 * @brief   同相IO定义-IO
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_io_pin_make(name, port, pin) \
	extern const port_io_pin_type name
#else
#define port_io_pin_make(name, port, pin) \
                                          \
	void name##_pin_en(void);             \
	void name##_pin_dis(void);            \
	void name##_pin_out(uint8_t st);      \
	void name##_pin_tog(void);            \
	uint8_t name##_pin_out_st(void);      \
	uint8_t name##_pin_in_st(void);       \
	void name##_dir_in_ft(void);          \
	void name##_dir_in_up(void);          \
	void name##_dir_out_pp(void);         \
	void name##_dir_out_od(void);         \
                                          \
	void name##_pin_en(void)              \
	{                                     \
		gpio_out_high(port, pin);         \
	}                                     \
	void name##_pin_dis(void)             \
	{                                     \
		gpio_out_low(port, pin);          \
	}                                     \
	void name##_pin_out(uint8_t st)       \
	{                                     \
		gpio_out_set(port, pin, st);      \
	}                                     \
	void name##_pin_tog(void)             \
	{                                     \
		gpio_out_tog(port, pin);          \
	}                                     \
	uint8_t name##_pin_out_st(void)       \
	{                                     \
		return gpio_out_get(port, pin);   \
	}                                     \
	uint8_t name##_pin_in_st(void)        \
	{                                     \
		return gpio_in_get(port, pin);    \
	}                                     \
	void name##_dir_in_ft(void)           \
	{                                     \
		gpio_dir_in_ft(port, pin);        \
	}                                     \
	void name##_dir_in_up(void)           \
	{                                     \
		gpio_dir_in_up(port, pin);        \
	}                                     \
	void name##_dir_out_pp(void)          \
	{                                     \
		gpio_dir_out_pp(port, pin);       \
	}                                     \
	void name##_dir_out_od(void)          \
	{                                     \
		gpio_dir_out_od(port, pin);       \
	}                                     \
	const port_io_pin_type name = {       \
		name##_pin_en,                    \
		name##_pin_dis,                   \
		name##_pin_out,                   \
		name##_pin_tog,                   \
		name##_pin_out_st,                \
		name##_pin_in_st,                 \
		name##_dir_in_ft,                 \
		name##_dir_in_up,                 \
		name##_dir_out_pp,                \
		name##_dir_out_od}
#endif

/*******************************************************************************
 * @brief   反相IO定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_nio_pin_make(name, port, pin) \
	extern const port_io_pin_type name
#else
#define port_nio_pin_make(name, port, pin) \
                                           \
	void name##_pin_en(void);              \
	void name##_pin_dis(void);             \
	void name##_pin_out(uint8_t st);       \
	void name##_pin_tog(void);             \
	uint8_t name##_pin_out_st(void);       \
	uint8_t name##_pin_in_st(void);        \
	void name##_dir_in_ft(void);           \
	void name##_dir_in_up(void);           \
	void name##_dir_out_pp(void);          \
	void name##_dir_out_od(void);          \
                                           \
	void name##_pin_en(void)               \
	{                                      \
		gpio_out_low(port, pin);           \
	}                                      \
	void name##_pin_dis(void)              \
	{                                      \
		gpio_out_high(port, pin);          \
	}                                      \
	void name##_pin_out(uint8_t st)        \
	{                                      \
		gpio_out_set(port, pin, !st);      \
	}                                      \
	void name##_pin_tog(void)              \
	{                                      \
		gpio_out_tog(port, pin);           \
	}                                      \
	uint8_t name##_pin_out_st(void)        \
	{                                      \
		return !gpio_out_get(port, pin);   \
	}                                      \
	uint8_t name##_pin_in_st(void)         \
	{                                      \
		return !gpio_in_get(port, pin);    \
	}                                      \
	void name##_dir_in_ft(void)            \
	{                                      \
		gpio_dir_in_ft(port, pin);         \
	}                                      \
	void name##_dir_in_up(void)            \
	{                                      \
		gpio_dir_in_up(port, pin);         \
	}                                      \
	void name##_dir_out_pp(void)           \
	{                                      \
		gpio_dir_out_pp(port, pin);        \
	}                                      \
	void name##_dir_out_od(void)           \
	{                                      \
		gpio_dir_out_od(port, pin);        \
	}                                      \
	const port_io_pin_type name = {        \
		name##_pin_en,                     \
		name##_pin_dis,                    \
		name##_pin_out,                    \
		name##_pin_tog,                    \
		name##_pin_out_st,                 \
		name##_pin_in_st,                  \
		name##_dir_in_ft,                  \
		name##_dir_in_up,                  \
		name##_dir_out_pp,                 \
		name##_dir_out_od}
#endif

/*******************************************************************************
 * @brief   同相OUT定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_out_pin_make(name, port, pin) \
	extern const port_out_pin_type name
#else
#define port_out_pin_make(name, port, pin) \
                                           \
	void name##_pin_en(void);              \
	void name##_pin_dis(void);             \
	void name##_pin_out(uint8_t st);       \
	void name##_pin_tog(void);             \
	uint8_t name##_pin_out_st(void);       \
	void name##_dir_out_pp(void);          \
	void name##_dir_out_od(void);          \
                                           \
	void name##_pin_en(void)               \
	{                                      \
		gpio_out_high(port, pin);          \
	}                                      \
	void name##_pin_dis(void)              \
	{                                      \
		gpio_out_low(port, pin);           \
	}                                      \
	void name##_pin_out(uint8_t st)        \
	{                                      \
		gpio_out_set(port, pin, st);       \
	}                                      \
	void name##_pin_tog(void)              \
	{                                      \
		gpio_out_tog(port, pin);           \
	}                                      \
	uint8_t name##_pin_out_st(void)        \
	{                                      \
		return gpio_out_get(port, pin);    \
	}                                      \
	void name##_dir_out_pp(void)           \
	{                                      \
		gpio_dir_out_pp(port, pin);        \
	}                                      \
	void name##_dir_out_od(void)           \
	{                                      \
		gpio_dir_out_od(port, pin);        \
	}                                      \
	const port_out_pin_type name = {       \
		name##_pin_en,                     \
		name##_pin_dis,                    \
		name##_pin_out,                    \
		name##_pin_tog,                    \
		name##_pin_out_st,                 \
		name##_dir_out_pp,                 \
		name##_dir_out_od}
#endif

/*******************************************************************************
 * @brief   反相OUT定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_nout_pin_make(name, port, pin) \
	extern const port_out_pin_type name
#else
#define port_nout_pin_make(name, port, pin) \
                                            \
	void name##_pin_en(void);               \
	void name##_pin_dis(void);              \
	void name##_pin_out(uint8_t st);        \
	void name##_pin_tog(void);              \
	uint8_t name##_pin_out_st(void);        \
	void name##_dir_out_pp(void);           \
	void name##_dir_out_od(void);           \
                                            \
	void name##_pin_en(void)                \
	{                                       \
		gpio_out_low(port, pin);            \
	}                                       \
	void name##_pin_dis(void)               \
	{                                       \
		gpio_out_high(port, pin);           \
	}                                       \
	void name##_pin_out(uint8_t st)         \
	{                                       \
		gpio_out_set(port, pin, (!st));     \
	}                                       \
	void name##_pin_tog(void)               \
	{                                       \
		gpio_out_tog(port, pin);            \
	}                                       \
	uint8_t name##_pin_out_st(void)         \
	{                                       \
		return !gpio_out_get(port, pin);    \
	}                                       \
	void name##_dir_out_pp(void)            \
	{                                       \
		gpio_dir_out_pp(port, pin);         \
	}                                       \
	void name##_dir_out_od(void)            \
	{                                       \
		gpio_dir_out_od(port, pin);         \
	}                                       \
	const port_out_pin_type name = {        \
		name##_pin_en,                      \
		name##_pin_dis,                     \
		name##_pin_out,                     \
		name##_pin_tog,                     \
		name##_pin_out_st,                  \
		name##_dir_out_pp,                  \
		name##_dir_out_od}
#endif

/*******************************************************************************
 * @brief   同相IN定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_in_pin_make(name, port, pin) \
	extern const port_in_pin_type name
#else
#define port_in_pin_make(name, port, pin) \
                                          \
	uint8_t name##_pin_in_st(void);       \
	void name##_dir_in_ft(void);          \
	void name##_dir_in_up(void);          \
	void name##_dir_in_dn(void);          \
                                          \
	uint8_t name##_pin_in_st(void)        \
	{                                     \
		return gpio_in_get(port, pin);    \
	}                                     \
	void name##_dir_in_ft(void)           \
	{                                     \
		gpio_dir_in_ft(port, pin);        \
	}                                     \
	void name##_dir_in_up(void)           \
	{                                     \
		gpio_dir_in_up(port, pin);        \
	}                                     \
	void name##_dir_in_dn(void)           \
	{                                     \
		gpio_dir_in_dn(port, pin);        \
	}                                     \
	const port_in_pin_type name = {       \
		name##_pin_in_st,                 \
		name##_dir_in_ft,                 \
		name##_dir_in_up,                 \
		name##_dir_in_dn,                 \
	}
#endif

/*******************************************************************************
 * @brief   反相IN定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define port_nin_pin_make(name, port, pin) \
	extern const port_in_pin_type name
#else
#define port_nin_pin_make(name, port, pin) \
                                           \
	uint8_t name##_pin_in_st(void);        \
	void name##_dir_in_ft(void);           \
	void name##_dir_in_up(void);           \
	void name##_dir_in_dn(void);           \
                                           \
	uint8_t name##_pin_in_st(void)         \
	{                                      \
		return !gpio_in_get(port, pin);    \
	}                                      \
	void name##_dir_in_ft(void)            \
	{                                      \
		gpio_dir_in_ft(port, pin);         \
	}                                      \
	void name##_dir_in_up(void)            \
	{                                      \
		gpio_dir_in_up(port, pin);         \
	}                                      \
	void name##_dir_in_dn(void)            \
	{                                      \
		gpio_dir_in_dn(port, pin);         \
	}                                      \
	const port_in_pin_type name = {        \
		name##_pin_in_st,                  \
		name##_dir_in_ft,                  \
		name##_dir_in_up,                  \
		name##_dir_in_dn,                  \
	}
#endif

	/*******************************************************************************
	 * @brief   外部扩展IO
	 *******************************************************************************/
	extern uint8_t ext_port_out[][8];
	extern uint8_t ext_port_in[];
/*******************************************************************************
 * @brief   同相IO定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define ext_io_pin_make(name, port, pin) \
	extern const port_fun_pin_type name
#else
#define ext_io_pin_make(name, port, pin)                    \
                                                            \
	void name##_pin_en(void);                               \
	void name##_pin_dis(void);                              \
	void name##_pin_out(uint8_t st);                        \
	void name##_pin_tog(void);                              \
	uint8_t name##_pin_out_st(void);                        \
	uint8_t name##_pin_in_st(void);                         \
	void name##_mode_set(char pm);                          \
                                                            \
	void name##_pin_en(void)                                \
	{                                                       \
		ext_port_out[port][pin] = 1;                        \
	}                                                       \
	void name##_pin_dis(void)                               \
	{                                                       \
		ext_port_out[port][pin] = 0;                        \
	}                                                       \
	void name##_pin_out(uint8_t st)                         \
	{                                                       \
		ext_port_out[port][pin] = st;                       \
	}                                                       \
	void name##_pin_tog(void)                               \
	{                                                       \
		ext_port_out[port][pin] = !ext_port_out[port][pin]; \
	}                                                       \
	uint8_t name##_pin_out_st(void)                         \
	{                                                       \
		return ext_port_out[port][pin];                     \
	}                                                       \
	uint8_t name##_pin_in_st(void)                          \
	{                                                       \
		return (ext_port_in[port] >> pin) & 1u;             \
	}                                                       \
	void name##_mode_set(char pm)                           \
	{                                                       \
	}                                                       \
	const port_fun_pin_type name = {                        \
		name##_pin_en,                                      \
		name##_pin_dis,                                     \
		name##_pin_out,                                     \
		name##_pin_tog,                                     \
		name##_pin_out_st,                                  \
		name##_pin_in_st,                                   \
		name##_mode_set}
#endif

/*******************************************************************************
 * @brief   反相IO定义
 *******************************************************************************/
#ifndef PORT_PIN_CTEAT
#define ext_nio_pin_make(name, port, pin) \
	extern const port_fun_pin_type name
#else
#define ext_nio_pin_make(name, port, pin)                   \
                                                            \
	void name##_pin_en(void);                               \
	void name##_pin_dis(void);                              \
	void name##_pin_out(uint8_t st);                        \
	void name##_pin_tog(void);                              \
	uint8_t name##_pin_out_st(void);                        \
	uint8_t name##_pin_in_st(void);                         \
	void name##_mode_set(char pm);                          \
                                                            \
	void name##_pin_en(void)                                \
	{                                                       \
		ext_port_out[port][pin] = 0;                        \
	}                                                       \
	void name##_pin_dis(void)                               \
	{                                                       \
		ext_port_out[port][pin] = 1;                        \
	}                                                       \
	void name##_pin_out(uint8_t st)                         \
	{                                                       \
		ext_port_out[port][pin] = !st;                      \
	}                                                       \
	void name##_pin_tog(void)                               \
	{                                                       \
		ext_port_out[port][pin] = !ext_port_out[port][pin]; \
	}                                                       \
	uint8_t name##_pin_out_st(void)                         \
	{                                                       \
		return !ext_port_out[port][pin];                    \
	}                                                       \
	uint8_t name##_pin_in_st(void)                          \
	{                                                       \
		return !((ext_port_in[port] >> pin) & 1u);          \
	}                                                       \
	void name##_mode_set(char pm)                           \
	{                                                       \
	}                                                       \
	const port_fun_pin_type name = {                        \
		name##_pin_en,                                      \
		name##_pin_dis,                                     \
		name##_pin_out,                                     \
		name##_pin_tog,                                     \
		name##_pin_out_st,                                  \
		name##_pin_in_st,                                   \
		name##_mode_set}
#endif

#ifdef __cplusplus
}
#endif

#endif
